home *** CD-ROM | disk | FTP | other *** search
/ Nikkei Mac 11 / NIKKEI-MAC-CD-VOL-11-1998-03.ISO.7z / NIKKEI-MAC-CD-VOL-11-1998-03.ISO / オンラインソフト / 3.デスクトップを楽しく / DarkSide of the Mac 4.2.sit / DarkSide of the Mac 4.2 / SampleFaders / Fader.c next >
C/C++ Source or Header  |  1994-08-18  |  12KB  |  472 lines

  1. /*
  2.     DarkSide - a 7.0 dependant, system clean expandable screen saver.
  3.     
  4.     copyright ゥハ1990-1994 by Tom Dowdy
  5.     All rights reserved.
  6.     
  7.     This fader shell serves to dispatch requests from the main DarkSide code
  8.     into the appropriate entry points.
  9. */
  10. #include <StdArg.h>
  11. #include <Memory.h>
  12. #include <Packages.h>
  13. #include <Errors.h>
  14.  
  15. #include "Fader.h"
  16. #ifdef THINK_C
  17.     #include <SetupA4.h>
  18. #endif
  19.  
  20. /* ------------------------------------------------------------------------    */
  21. /* GLOBAL HANDLING ROUTINES */
  22. /* ------------------------------------------------------------------------    */
  23. void    DebugLongInt(long aLong);
  24.  
  25. #ifndef THINK_C
  26.     OSErr    CreateA5World(Ptr * a5World);
  27.     void    DisposeA5World(Ptr a5World, Ptr appA5);
  28. #endif
  29.  
  30. /* ------------------------------------------------------------------------    */
  31. #ifdef THINK_C
  32.     OSErr    main(long selector, Ptr *a5World, MachineInfoPtr machineInfo, ...)
  33. #else
  34.     OSErr    FaderEntry(long selector, Ptr *a5World, MachineInfoPtr machineInfo, ...)
  35. #endif
  36. {
  37.     OSErr    anErr = noErr;
  38.     va_list    nextArg;
  39.     
  40.  
  41.     #ifdef THINK_C
  42.         // Set up A4 so that we can use global variables...
  43.         RememberA0();
  44.         SetUpA4();
  45.     #endif
  46.     
  47.     // start stripping optional arguments
  48.     va_start(nextArg, machineInfo);
  49.     
  50.     switch(selector)
  51.         {
  52.         case preflightFader:
  53.             {
  54.             long    *minTicks, *maxTicks;
  55.             
  56.             minTicks = va_arg(nextArg, long*);
  57.             maxTicks = va_arg(nextArg, long*);
  58.             
  59.             #ifndef THINK_C
  60.                 anErr = CreateA5World(a5World);
  61.             #endif
  62.             
  63.             if (anErr == noErr)
  64.                 {
  65.                 #ifndef THINK_C
  66.                     (void) SetA5((long) *a5World);
  67.                 #endif
  68.                 
  69.                 BlockMove(machineInfo->applicationQD, &qd, sizeof(qd));
  70.                 anErr = PreflightFader(machineInfo, minTicks, maxTicks);
  71.                 BlockMove(&qd, machineInfo->applicationQD, sizeof(qd));
  72.                 }
  73.             }
  74.             break;
  75.             
  76.         case initializeFader:
  77.             #ifndef THINK_C
  78.                 (void) SetA5((long) *a5World);
  79.             #endif
  80.  
  81.             BlockMove(machineInfo->applicationQD, &qd, sizeof(qd));
  82.             anErr = InitializeFader(machineInfo);
  83.             BlockMove(&qd, machineInfo->applicationQD, sizeof(qd));
  84.             break;
  85.             
  86.         case idleFader:
  87.             #ifndef THINK_C
  88.                 (void) SetA5((long) *a5World);
  89.             #endif
  90.  
  91.             anErr = IdleFader(machineInfo);
  92.             break;
  93.             
  94.         case disposeFader:
  95.             {
  96.             
  97.             #ifndef THINK_C
  98.                 (void) SetA5((long) *a5World);
  99.             #endif
  100.  
  101.             BlockMove(machineInfo->applicationQD, &qd, sizeof(qd));
  102.             anErr = DisposeFader(machineInfo);
  103.             BlockMove(&qd, machineInfo->applicationQD, sizeof(qd));
  104.  
  105.             #ifndef THINK_C
  106.                 DisposeA5World(*a5World, (Ptr)machineInfo->applicationA5);
  107.             #endif
  108.             
  109.             }
  110.             break;
  111.  
  112.         case updateFader:
  113.             #ifndef THINK_C
  114.                 (void) SetA5((long) *a5World);
  115.             #endif
  116.             anErr = UpdateFader(machineInfo);
  117.             break;
  118.             
  119.         case hitFader:
  120.             {
  121.             DialogPtr    dPtr;
  122.             long        itemHit;
  123.             long        itemOffset;
  124.                         
  125.             dPtr         = va_arg(nextArg, DialogPtr);
  126.             itemHit     = va_arg(nextArg, long);
  127.             itemOffset     = va_arg(nextArg, long);
  128.  
  129.             anErr = HitFader(machineInfo, dPtr, itemHit, itemOffset);            
  130.             }
  131.             
  132.             break;
  133.             
  134.         default:
  135.             // function not found error
  136.             anErr = fnfErr;
  137.             break;
  138.         }
  139.         
  140.     va_end(nextArg);
  141.     
  142.     #ifdef THINK_C
  143.         RestoreA4();
  144.     #else
  145.         (void) SetA5(machineInfo->applicationA5);
  146.     #endif
  147.     
  148.     return(anErr);    
  149.     
  150. } // FaderEntry
  151.  
  152. /* ------------------------------------------------------------------------    */
  153. /* DEBUGGING ROUTINES                             */
  154. /* ------------------------------------------------------------------------    */
  155. void DebugLongInt(long theLong)
  156. {
  157.     Str255 theString;
  158.     
  159.     NumToString(theLong, theString);
  160.     DebugStr(theString);
  161.     
  162. } // DebugLongInt
  163.  
  164.  
  165. /* ------------------------------------------------------------------------    */
  166. /* FADER UTILS                                                                 */
  167. /* ------------------------------------------------------------------------    */
  168.  
  169. Handle    BestNewHandle(Size    theSize)
  170. /*
  171.     Tries to get the handle from the temp memory first, if that fails, it goes
  172.     to the application.
  173. */
  174. {
  175.     Handle theHandle;
  176.     OSErr    anErr;
  177.     
  178.     theHandle = TempNewHandle(theSize, &anErr);
  179.     if (theHandle == nil)
  180.         theHandle = NewHandle(theSize);
  181.         
  182.     return(theHandle);
  183.     
  184. } // BestNewHandle
  185.  
  186. /* ------------------------------------------------------------------------    */
  187.  
  188. RgnHandle    BestNewRgn()
  189. /*
  190.     Tries to get a rgn handle from the temp memory first, if that fails, it goes
  191.     to the application.  Needs enough room in the app heap to create the region
  192.     in the first place.
  193. */
  194. {
  195.     RgnHandle     theRgn;
  196.     OSErr        anErr;
  197.     
  198.     // make a region
  199.     theRgn = NewRgn();
  200.     if (theRgn != nil)
  201.         {
  202.         RgnHandle    theHandle;
  203.         short        regionSize;
  204.         
  205.         // try to make something the same size in the temp memory
  206.         regionSize = GetHandleSize((Handle) theRgn);
  207.         theHandle = (RgnHandle) TempNewHandle(regionSize, &anErr);
  208.         if (anErr == noErr)
  209.             {
  210.             // if we get it, use that one for our region
  211.             BlockMove(*theRgn, *theHandle, regionSize);
  212.             DisposeRgn(theRgn);
  213.             theRgn = theHandle;
  214.             }
  215.         }
  216.         
  217.     return(theRgn);
  218.     
  219. } // BestNewRgn
  220.  
  221.  
  222.  
  223. /* ------------------------------------------------------------------------    */
  224.  
  225. short    Rnd(long max)
  226. /*
  227.     Returns a number > 0 and < max
  228. */
  229. {
  230. unsigned long value;
  231.  
  232.     value = (unsigned short)max * (unsigned short)Random();
  233.     value >>= 16;
  234.     return(value);
  235.     
  236. } // Rnd
  237.  
  238. /* ------------------------------------------------------------------------    */
  239. void PlaceRectOnScreen(
  240.     MachineInfoPtr machineInfo,    // give info about the machine here
  241.     short width,                // width of rect, can be 0
  242.     short height,                // height of rect, can be 0
  243.     Rect * placedRect,            // Placed rect is returned here
  244.     Rect * margins,                // margins around screen, can be nil
  245.     short * whichScreen)        // screen index returned here, can be nil
  246. {
  247.     Rect        screenRect;
  248.     short        pickScreen;
  249.  
  250.     // pick a random screen    
  251.     pickScreen = Rnd(machineInfo->numScreens);
  252.     screenRect = machineInfo->theScreens[pickScreen].bounds;
  253.     if (whichScreen != nil)
  254.         *whichScreen = pickScreen;
  255.         
  256.     if (margins != nil)
  257.         {
  258.         screenRect.top += margins->top;
  259.         screenRect.left += margins->left;
  260.         screenRect.bottom -= margins->bottom;
  261.         screenRect.right -= margins->right;
  262.         }
  263.         
  264.     screenRect.right -= width;
  265.     screenRect.bottom -= height;
  266.     
  267.     if (placedRect != nil)
  268.         {
  269.         placedRect->top = screenRect.top + Rnd(screenRect.bottom - screenRect.top);
  270.         placedRect->left = screenRect.left + Rnd(screenRect.right - screenRect.left);
  271.         placedRect->bottom = placedRect->top + height;
  272.         placedRect->right = placedRect->left + width;
  273.         }
  274.         
  275. } // PlaceRectOnScreen
  276.  
  277. #ifndef THINK_C
  278. /* ------------------------------------------------------------------------    */
  279. /* FUN A5 STUFF - See Tech note 256 for details                             */
  280. /* ------------------------------------------------------------------------    */
  281. long A5Size(); 
  282. void A5Init(Ptr theA5);
  283.  
  284. OSErr    CreateA5World(Ptr * a5World)
  285. {
  286.     OSErr    anErr;
  287.     Ptr        theWorld = nil;
  288.     Handle    worldHandle;
  289.     
  290.     worldHandle = BestNewHandle(A5Size());
  291.     anErr = MemError();
  292.     if (anErr == noErr)
  293.         {
  294.         HLockHi(worldHandle);
  295.         theWorld = *worldHandle;
  296.         
  297.         theWorld += + A5Size() - 32;
  298.         A5Init(theWorld);
  299.         
  300.         // very important if anyone wants to call SwapMMUMode
  301.         theWorld = StripAddress(theWorld);
  302.         }
  303.     *a5World = theWorld;
  304.     
  305.     return(anErr);
  306.     
  307. } // CreateA5World
  308.  
  309. /* ------------------------------------------------------------------------    */
  310. void    DisposeA5World(Ptr a5World, Ptr appA5)
  311. {
  312.     
  313.     (void) SetA5((long) appA5);
  314.     
  315.     {
  316.     Handle    theHandle = RecoverHandle(a5World - A5Size() + 32);
  317.     
  318.     DisposHandle(theHandle);
  319.     }
  320.     
  321. } // DisposeA5World
  322. #endif
  323.  
  324. #ifdef THINK_C
  325. /* ------------------------------------------------------------------------    */
  326. /* CALLBACK WRAPPERS
  327. /* ------------------------------------------------------------------------    */
  328. OSErr    WritePreferencesHandle(MachineInfoPtr machineInfo, Handle h, ResType theType)
  329. {
  330.     OSErr    anErr;
  331.     long    curA5;
  332.     long    loader;
  333.     
  334.     curA5 = SetA5(machineInfo->applicationA5);
  335.     loader = (long) machineInfo->callbackLoader;
  336.     asm {
  337.         move.l theType, -(SP)
  338.         move.l h, -(SP)
  339.         move.l loader, a0
  340.         moveq #0, d0
  341.         pea @returnAddress
  342.         move.l #0x08000004, -(SP)
  343.         jmp (a0)
  344.     @returnAddress:
  345.         move.w d0, anErr
  346.         add #8, SP
  347.     }
  348.     SetA5(curA5);
  349.     return(anErr);
  350.     
  351. } // WritePreferencesHandle
  352.  
  353. /* ------------------------------------------------------------------------    */
  354. OSErr    ReadPreferencesHandle(MachineInfoPtr machineInfo, Handle *h, ResType theType)
  355. {
  356.     OSErr    anErr;
  357.     long    curA5;
  358.     long    loader;
  359.     
  360.     curA5 = SetA5(machineInfo->applicationA5);
  361.     loader = (long) machineInfo->callbackLoader;
  362.     asm {
  363.         move.l theType, -(SP)
  364.         move.l h, -(SP)
  365.         move.l loader, a0
  366.         moveq #0, d0
  367.         pea @returnAddress
  368.         move.l #0x08000008, -(SP)
  369.         jmp (a0)
  370.     @returnAddress:
  371.         move.w d0, anErr
  372.         add #8, SP
  373.     }
  374.     SetA5(curA5);
  375.     return(anErr);
  376.     
  377. } // ReadPreferencesHandle
  378.  
  379. /* ------------------------------------------------------------------------    */
  380. // While translating this code from MPW C to THINK C I found out that the calling conventions
  381. // of these languages seem to be different. If we have a short and a Boolean as below, THINK C
  382. // pushes them both into a longword, while MPW C uses a longword for each. Very confusing!
  383.  
  384. OSErr    PlayResourceSnd(MachineInfoPtr machineInfo, short theID, Boolean async)
  385. {
  386.     OSErr    anErr;
  387.     long    loader;
  388.     
  389.     loader = (long) machineInfo->callbackLoader;
  390.     asm {
  391.         moveq #0, d0
  392.         move.b async, d0                                // convert async to longword
  393.         move.l d0, -(SP)                                // and push it
  394.  
  395.         moveq #0, d0                                    // convert theID to longword
  396.         move.w theID, d0                                // and push it
  397.         move.l d0, -(SP)
  398.         
  399.         move.l loader, a0
  400.         moveq #0, d0
  401.         pea @returnAddress                                // push return address
  402.         move.l #0x0800000C, -(SP)                        // push selector code
  403.         jmp (a0)                                        // jump to callback loader
  404.     @returnAddress:
  405.         move.w d0, anErr                                // save result code                                
  406.         add #8, SP                                        // adjust stack
  407.     }
  408.     return anErr;
  409.     
  410. } // PlayResourceSnd
  411.  
  412. #else
  413.  
  414. /* ------------------------------------------------------------------------    */
  415. /* CALLBACK DEFINES
  416. /* ------------------------------------------------------------------------    */
  417. #pragma parameter __D0 DoWritePreferencesHandle(__A0)
  418. OSErr DoWritePreferencesHandle(Ptr M, Handle h, ResType theType) = 
  419.     { 0x7000, 0x487B, 0x000A, 0x2F3C, 0x0800, 0x0004, 0x4ED0};
  420. #pragma parameter __D0 DoReadPreferencesHandle(__A0)
  421. OSErr DoReadPreferencesHandle(Ptr M, Handle *h, ResType theType) = 
  422.     { 0x7000, 0x487B, 0x000A, 0x2F3C, 0x0800, 0x0008, 0x4ED0};
  423. #pragma parameter __D0 DoPlayResourceSnd(__A0)
  424. OSErr DoPlayResourceSnd(Ptr M, short theID, Boolean async) = 
  425.     { 0x7000, 0x487B, 0x000A, 0x2F3C, 0x0800, 0x000C, 0x4ED0};
  426.  
  427. /* ------------------------------------------------------------------------    */
  428. /* CALLBACK WRAPERS
  429. /* ------------------------------------------------------------------------    */
  430. OSErr    WritePreferencesHandle(MachineInfoPtr machineInfo, Handle h, ResType theType)
  431. {
  432.     OSErr    anErr;
  433.     long    curA5;
  434.     
  435.     curA5 = SetA5(machineInfo->applicationA5);
  436.     anErr = DoWritePreferencesHandle(machineInfo->callbackLoader, h, theType);
  437.     
  438.     SetA5(curA5);
  439.     return(anErr);
  440.     
  441. } // WritePreferencesHandle
  442.  
  443. /* ------------------------------------------------------------------------    */
  444. OSErr    ReadPreferencesHandle(MachineInfoPtr machineInfo, Handle *h, ResType theType)
  445. {
  446.     OSErr    anErr;
  447.     long    curA5;
  448.     
  449.     curA5 = SetA5(machineInfo->applicationA5);
  450.     anErr = DoReadPreferencesHandle(machineInfo->callbackLoader, h, theType);
  451.     
  452.     SetA5(curA5);
  453.     return(anErr);
  454.     
  455. } // ReadPreferencesHandle
  456.  
  457. /* ------------------------------------------------------------------------    */
  458. OSErr    PlayResourceSnd(MachineInfoPtr machineInfo, short theID, Boolean async)
  459. {
  460.     OSErr    anErr;
  461.     long    curA5;
  462.     
  463.     curA5 = SetA5(machineInfo->applicationA5);
  464.     anErr = DoPlayResourceSnd(machineInfo->callbackLoader, theID, async);
  465.     
  466.     SetA5(curA5);
  467.     return(anErr);
  468.     
  469. } // PlayResourceSnd
  470.  
  471. #endif
  472.